#include "GroupMemberListModel.h"
#include "../../global/QmlNames.h"

X_BEGIN_NAMESPACE

enum RoleNames {
    bareJid,
    nickName,
    photo,
    photoType,
    availableStatus,
    DATA_ROLE_MAX
};

const char* GroupMemberListModel::ROLE_NAMES[] = {
    "bareJid",
    "nickName",
    "photo",
    "photoType",
    "availableStatus"
};

/**
 * @class GroupMemberListModel
 * @brief 群成员列表模型
 *
 * 管理群组的成员列表。
 */

GroupMemberListModel::GroupMemberListModel(QObject* parent)
    : QAbstractListModel(parent)
    , d(new GroupMembersModelPrivate)
{
    for(int i = bareJid; i < DATA_ROLE_MAX; ++i){
        m_roleNames.insert(i, ROLE_NAMES[i]);
    }
}

GroupMemberListModel::GroupMemberListModel(const GroupMemberListModel &src)
    : QAbstractListModel(src.parent())
    , d(src.d)
{
    m_roleNames = src.m_roleNames;
}

GroupMemberListModel &GroupMemberListModel::operator =(const GroupMemberListModel &rhs)
{
    if(this != & rhs) this->d = rhs.d;

    return *this;
}

GroupMemberListModel::~GroupMemberListModel()
{

}

const char *GroupMemberListModel::qmlName()
{
    return QmlNames::SubModelType::SubModelType::GroupMemberListModel;
}

int GroupMemberListModel::rowCount(const QModelIndex &parent) const
{
    Q_UNUSED(parent)

    return d->m_members.size();
}

QVariant GroupMemberListModel::data(const QModelIndex &index, int role) const
{
    if(!index.isValid()) return QVariant();

    GroupMemberModel* member = d->m_members[index.row()];
    switch (role) {
        case bareJid:
            return member->bareJid();
        case nickName:
            return member->nickName();
        case photo:
            return member->photo();
        case photoType:
            return (int)member->photoType();
        case availableStatus:
            return (int)member->availableStatus();
        default:
            return QVariant("Not Implement.");
    }
}

QHash<int, QByteArray> GroupMemberListModel::roleNames() const
{
    return m_roleNames;
}

GroupMemberModel &GroupMemberListModel::addMember(const QString &bareJid, const QString &name, const QString &photo, PhotoType photoType)
{
    // 已存在，直接返回
    if(d->m_membersById.contains(bareJid)){
        return *d->m_membersById[bareJid];
    }

    // 插入列表
    GroupMemberModel* member = new GroupMemberModel(bareJid);
    (*member).setNickName(name)
            .setPhoto(photo)
            .setPhotoType(photoType)
            .setAvailableStatus(AvailableStatus::OffLine);

    d->m_membersById[bareJid] = member;

    bool inserted = false;
    for(int i = 0; i < d->m_members.size(); ++i){
        if(groupMemberLessThan(d->m_members[i], member)) continue;

        d->m_members.insert(i, member);
        inserted = true;
        break;
    }

    if(!inserted){
        d->m_members.append(member);
    }

    return *member;
}

GroupMemberModel &GroupMemberListModel::saveMember(const QString &bareJid, const QString &name, const QString &photo, PhotoType photoType)
{
    // 保存到数据库
    // TODO:

    // 增加到内存
    return addMember(bareJid, name, photo, photoType);
}

/**
 * @brief 统计在线人数情况
 * @return
 */
QString GroupMemberListModel::stats() const
{
    int online = 0;
    for(int i = 0; i < d->m_members.size(); ++i){
        AvailableStatus as = d->m_members[i]->availableStatus();
        if(as != AvailableStatus::Invisible && as != AvailableStatus::OffLine){
            online++;
        }
    }

    return QString::number(online) + "/" + QString::number(d->m_members.size());
}

bool GroupMemberListModel::groupMemberLessThan(const GroupMemberModel *m1, const GroupMemberModel *m2)
{
    return m1->bareJid() < m2->bareJid();
}

X_END_NAMESPACE
